package org.fengling.readingplatform.manager.service.impl;

import org.fengling.readingplatform.manager.mapper.ChapterMapper;
import org.fengling.readingplatform.manager.service.ChapterService;
import org.fengling.readingplatform.model.entity.novel.Chapter;
import org.fengling.readingplatform.model.entity.novel.ChapterUpdateInfo;
import org.fengling.readingplatform.model.vo.novel.ChapterVo;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.List;

@Service
public class ChapterServiceImpl implements ChapterService {

    @Autowired
    private ChapterMapper chapterMapper;

    // 章节添加的方法
    @Override
    public void saveChapter(Chapter chapter) {
        // 章节结构为一个双向链表,则章节添加的操作则是针对双向链表而言的
        // 章节结构为一个双向链表,此时的情况则是考虑双向链表
        // 首先获取章节结点的信息,得到其prevChapterId nextChapterId
        Long novelId = chapter.getNovelId();
        Long sortValue = chapter.getSortValue();
        Long chapterId;

        // 获取最新的章节信息
        ChapterUpdateInfo chapterUpdateInfo = chapterMapper.getLatestChapterInfo(novelId);
        Long latestChapterId = chapterUpdateInfo.getLatestChapterId();
        Long latestSortId = chapterUpdateInfo.getLatestSortId();
        Long prevChapterId = chapter.getPrevChapterId();
        Long nextChapterId = chapter.getNextChapterId();
        if(prevChapterId == null){
            prevChapterId = -1L;
        }
        if(nextChapterId == null){
            nextChapterId = -1L;
        }

        if(chapter.getChapterId() != null){
            chapterId = chapter.getChapterId();
        } else{
            chapterId = latestChapterId + 1L;
            chapter.setChapterId(chapterId);
        }

        if(latestSortId == 0){
            System.out.println("此时链表为空");
        } else if(sortValue == 1){
            // 插入在最前面的时
            nextChapterId = chapterMapper.findChapterId(novelId, sortValue);
            // 修改后继节点的前驱节点
            chapterMapper.changeNextChapter(novelId, nextChapterId, chapterId);
        } else if(sortValue <= latestSortId){
            // 插入的是中间节点时
            prevChapterId = chapterMapper.findChapterId(novelId, sortValue-1);
            nextChapterId = chapterMapper.findChapterId(novelId, sortValue);
            // 修改前驱节点的后继节点
            chapterMapper.changePrevChapter(novelId, prevChapterId, chapterId);
            // 修改后继节点的前驱节点
            chapterMapper.changeNextChapter(novelId, nextChapterId,  chapterId);
        } else{
            prevChapterId = chapterMapper.findChapterId(novelId, sortValue-1);
            // 修改前驱节点的后继节点
            chapterMapper.changePrevChapter(novelId, prevChapterId, chapterId);
        }

        chapter.setPrevChapterId(prevChapterId);
        chapter.setNextChapterId(nextChapterId);
        chapter.setIsDeleted(0);

        // 修改插入节点的后面的节点的排序标号+1
        chapterMapper.changeSortValue(novelId, sortValue, 1L);

        // 待数据处理完毕进行保存该章节,此时有两种可能性,1个是原本就存在该文章，另一种是需要插入该文章
        Integer count = chapterMapper.count(novelId, chapterId);
        if(count == 0) {
            // 此时应当是插入该章节
            chapterMapper.save(chapter);
            latestChapterId += 1L;
        } else{
            System.out.println(chapter);
            // 此时应当是更新该章节
            chapterMapper.update(chapter);
        }
        // 最后更新章节更新表,最新的章节标号加1，最新的排序标号需要1
        latestSortId += 1;
        chapterMapper.renewChapter(novelId, latestChapterId, latestSortId);
    }

    // 章节内容获取的方法
    @Override
    public Chapter getChapter(Long novelId, Long chapterId) {
        return chapterMapper.getChapter(novelId, chapterId);
    }

    // 章节回收的方法
    @Override
    public void deleteChapter(Long novelId, Long chapterId) {
        // 章节结构为一个双向链表,此时的情况则是考虑双向链表
        // 首先获取章节结点的信息,得到其prevChapterId nextChapterId
        Chapter chapter = chapterMapper.getChapter(novelId, chapterId);
        Long prevChapterId = chapter.getPrevChapterId();
        Long nextChapterId = chapter.getNextChapterId();
        Long sortValue = chapter.getSortValue();

        // 获取最新的章节信息
        ChapterUpdateInfo chapterUpdateInfo = chapterMapper.getLatestChapterInfo(novelId);
        Long latestChapterId = chapterUpdateInfo.getLatestChapterId();
        Long latestSortId = chapterUpdateInfo.getLatestSortId();

        if(prevChapterId == -1 && nextChapterId == -1){
            System.out.println("此时链表只有一个节点");
        } else if(prevChapterId == -1){
            // 如果正好是头节点,则删除头结点，后面的结点的前驱指向空结点
            chapterMapper.changeNextChapter(novelId, nextChapterId,  -1L);
        } else if(nextChapterId == -1){
            // 如果正好是尾结点,则删除尾结点，前面的结点的后继指向空结点
            chapterMapper.changePrevChapter(novelId, prevChapterId, -1L);
        } else {
            // 如果是中间结点，则删除该结点，前驱结点的尾指针指向删除结点的后继结点，后继结点的头指针指向删除结点的前驱结点
            chapterMapper.deleteChapter(novelId, chapterId);
            chapterMapper.changePrevChapter(novelId, prevChapterId, nextChapterId);
            chapterMapper.changeNextChapter(novelId, nextChapterId, prevChapterId);
        }

        // 将该节点放入回收站中，需要将前后指针设置为空，将排序标号设置为-1，将删除标号设置为1
        chapter.setSortValue(-1L);
        chapter.setPrevChapterId(-1L);
        chapter.setNextChapterId(-1L);
        chapter.setIsDeleted(1);
        chapterMapper.update(chapter);


        // 修改删除节点后面的节点的排序标号-1
        chapterMapper.changeSortValue(novelId, sortValue, -1L);

        // 最后更新章节更新表,最新的章节标号不变，最新的排序标号需要-1
        chapterMapper.renewChapter(novelId, latestChapterId, latestSortId-1);
    }


    // 查询相应符合要求的章节
    @Override
    public List<ChapterVo> getChapterList(Long novelId, Integer isDeleted) {
        return chapterMapper.getChapterList(novelId, isDeleted);
    }

    // 状态改变方式
    @Override
    public void changeStatus(Long novelId, Long chapterId, Integer isDeleted) {
        chapterMapper.changeStatus(novelId, chapterId, isDeleted);
    }

    // 删除文章的方式
    @Override
    public void delete(Long novelId, Long chapterId) {
        chapterMapper.delete(novelId, chapterId);
    }

    // 更新文章信息的方式
    @Override
    public ChapterUpdateInfo getChapterUpdateInfo(Long novelId) {
        return chapterMapper.getLatestChapterInfo(novelId);
    }

    // 更新文章的方式
    @Override
    public void updateChapter(Chapter chapter) {
        Long novelId = chapter.getNovelId();
        Long chapterId = -1L;
        ChapterUpdateInfo chapterUpdateInfo = chapterMapper.getLatestChapterInfo(novelId);
        Long latestSortId = chapterUpdateInfo.getLatestSortId();
        Long latestChapterId = chapterUpdateInfo.getLatestChapterId();
        if(chapter.getChapterId() != null){
            chapterMapper.update(chapter);
        } else{
            chapterId = latestChapterId + 1;
            chapter.setChapterId(chapterId);
            chapterMapper.renewChapter(novelId, latestChapterId + 1, latestSortId);
            chapterMapper.save(chapter);
        }
    }
}
